package com.novunda.platform.services;

import java.util.List;

import com.novunda.platform.common.handler.LogCallBack;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import com.novunda.platform.common.exception.NovException;
import com.novunda.platform.common.utils.UserUtils;
import com.novunda.platform.entities.Log;
import com.novunda.platform.entities.Office;
import com.novunda.platform.repositories.OfficeRepository;

import net.sourceforge.pinyin4j.format.exception.BadHanyuPinyinOutputFormatCombination;

/**
 * 机构Service
 * 
 * @author slacrey
 * @version 2013-5-29
 * @modify FJ
 */
@Service
@Transactional(readOnly = true)
public class OfficeService extends BaseService {

	/**
	 * . 机构dao
	 */
	@Autowired
	private OfficeRepository officeRepository;

	/**
	 * . 功能说明：根据id获取机构
	 * 
	 * @param id
	 *            机构id
	 * @return
	 */
	public Office get(Long id) {
		officeRepository.clear();
		return officeRepository.findOne(id);
	}

	/**
	 * . 功能说明：查询所有机构
	 * 
	 * @return
	 */
	public List<Office> findAll() {
		return UserUtils.getOfficeList();
	}

	/**
	 * . 功能说明：保存机构
	 * 
	 * @param office
	 *            机构实体对象
	 * @throws BadHanyuPinyinOutputFormatCombination
	 */
	@Transactional(readOnly = false)
	public void save(final Office office) throws BadHanyuPinyinOutputFormatCombination {
		handler.doHandler(new LogCallBack() {
            @Override
            public Object doHandler() {
            	office.setParent(get(office.getParent().getId()));
        		// 获取修改前的parentIds，用于更新子节点的parentIds
        		String oldParentIds = office.getParentIds();
        		office.setParentIds(office.getParent().getParentIds() + office.getParent().getId() + ",");
        		officeRepository.clear();
        		Office of = officeRepository.save(office);
        		if (null == office.getId()) {
        			of.setCode(of.getCode() + of.getId());
        			officeRepository.save(of);
        		}
        		// 更新子节点 parentIds
        		List<Office> list = officeRepository.findByParentIdsLike("%," + office.getId() + ",%");
        		for (Office e : list) {
        			e.setParentIds(e.getParentIds().replace(oldParentIds, office.getParentIds()));
        		}
        		officeRepository.save(list);
        		UserUtils.removeCache(UserUtils.CACHE_OFFICE_LIST);
                return null;
            }

            @Override
            public Log generate() {
                Log log = new Log();
                String operation = office.getId() == null ? "添加" : "修改";
                log.setType(operation);
                String name = operation + (office.getType().equals("1") ? "机构" : "部门");
                log.setName(name);
                log.setDescription(name + "：" + office.getName());
                return log;
            }

            @Override
            public boolean forceLog() {
                return false;
            }
        });
		
	}

	/**
	 * . 功能说明：删除机构
	 * 
	 * @param id
	 *            机构id
	 */
	@Transactional(readOnly = false)
	public void delete(final Long id) {
		handler.doHandler(new LogCallBack() {
            @Override
            public Object doHandler() {
            	officeRepository.deleteById(id, "%," + id + ",%");
        		UserUtils.removeCache(UserUtils.CACHE_OFFICE_LIST);
                return null;
            }

            @Override
            public Log generate() {
            	officeRepository.clear();
        		Office office = officeRepository.findOne(id);
                Log log = new Log();
                log.setType("删除");
                String name = "删除" + (office.getType().equals("1") ? "机构" : "部门");
                log.setName(name);
                log.setDescription(name + "：" + office.getName());
                return log;
            }

            @Override
            public boolean forceLog() {
                return false;
            }
        });
		
	}

	/**
	 * . 功能说明：保存一次
	 * 
	 * @param office
	 *            机构实体
	 */
	@Transactional(readOnly = false)
	public void saveOnce(final Office office) {
		// String oldParentIds = office.getParentIds(); //
		// 获取修改前的parentIds，用于更新子节点的parentIds
		handler.doHandler(new LogCallBack() {
            @Override
            public Object doHandler() {
            	office.setParentIds(office.getParent().getParentIds() + office.getParent().getId() + ",");
        		officeRepository.clear();
        		officeRepository.save(office);
                return null;
            }

            @Override
            public Log generate() {
                Log log = new Log();
                log.setType("保存");
                String name = "保存" + (office.getType().equals("1") ? "机构" : "部门");
                log.setName(name);
                log.setDescription(name + "：" + office.getName());
                return log;
            }

            @Override
            public boolean forceLog() {
                return false;
            }
        });
		
	}

	/**
	 * . 功能说明：通过机构名查询机构
	 * 
	 * @param name
	 *            机构名
	 * @return
	 */
	public Office getOfficeByName(String name) {
		officeRepository.clear();
		return officeRepository.findByName(name);
	}
	
	/**
	 * .
	 *功能说明：通过所属机构查询该部门是否存在
	 * @param name 部门名
	 * @param parentId 父id
	 * @return
	 */
	public Office getOfficeByNameAndTypeAndParent(String name, long parentId) {
		officeRepository.clear();
		return officeRepository.findOfficeByNameAndTypeAndParent(name, parentId);
	}
	
	/**
	 * .
	 *功能说明：接口调用添加机构
	 * @param office 机构实体
	 * @return
	 * @throws NovException
	 */
	@Transactional(readOnly = false)
	public Office justSave(final Office office) throws NovException {
		try {
			return (Office)handler.doHandler(new LogCallBack() {
	            @Override
	            public Object doHandler() {
	            	officeRepository.clear();
	    			Office savedOffice = officeRepository.save(office);
	    			// 保存后获得id，重新设置机构编码，再保存
	    			savedOffice.setCode(office.getCode() + office.getId());
	    			return officeRepository.save(savedOffice);
	            }

	            @Override
	            public Log generate() {
	                Log log = new Log();
	                log.setType("保存");
	                String name = "保存" + (office.getType().equals("1") ? "机构" : "部门");
	                log.setName(name);
	                log.setDescription(name + "：" + office.getName());
	                return log;
	            }

	            @Override
	            public boolean forceLog() {
	                return false;
	            }
	        });
			
		} catch(Exception e) {
			throw new NovException(e.getMessage(), e);
		}
	}

}
